import React, { useEffect, useState, useRef, useMemo, useCallback } from 'react'
import { useNavigate } from 'react-router-dom'
import { visitorAPI, request } from '../api/request'

// Add a utility function for preloading images with AbortController support
const preloadImage = (src: string, signal?: AbortSignal): Promise<void> => {
  return new Promise((resolve, reject) => {
    const img = new Image();
    img.src = src;
    img.onload = () => resolve();
    img.onerror = () => reject();
    
    if (signal) {
      signal.addEventListener('abort', () => {
        img.src = '';
        reject(new Error('Image loading aborted'));
      });
    }
  });
};

// Add DNS prefetching component for faster image loading
const DNSPrefetch: React.FC = () => {
  return (
    <>
      <link rel="dns-prefetch" href="https://knowyou.tos-cn-guangzhou.volces.com" />
      <link rel="preconnect" href="https://knowyou.tos-cn-guangzhou.volces.com" crossOrigin="anonymous" />
      <link rel="dns-prefetch" href="https://images.unsplash.com" />
      <link rel="preconnect" href="https://images.unsplash.com" crossOrigin="anonymous" />
    </>
  );
};

// Add progressive image component
const ProgressiveImage = React.memo(({ 
  src, 
  alt, 
  className = '',
  placeholderColor = '#333',
  width,
  height,
  imgStyle = {},
  lazy = true
}: { 
  src: string; 
  alt: string; 
  className?: string;
  placeholderColor?: string;
  width?: number;
  height?: number;
  imgStyle?: React.CSSProperties;
  lazy?: boolean;
}) => {
  const [isLoaded, setIsLoaded] = useState(false);
  const [error, setError] = useState(false);
  const imgRef = useRef<HTMLImageElement>(null);
  
  useEffect(() => {
    // Reset states when src changes
    setIsLoaded(false);
    setError(false);
    
    // Set up intersection observer for proper lazy loading
    if (!lazy) {
      return;
    }

    const observer = new IntersectionObserver((entries) => {
      entries.forEach(entry => {
        if (entry.isIntersecting && imgRef.current) {
          const img = imgRef.current;
          
          // Only set src if it hasn't been set yet (data-src still exists)
          if (img.dataset.src && !img.src.includes(img.dataset.src)) {
            img.src = img.dataset.src;
            observer.unobserve(img);
          }
        }
      });
    }, {
      rootMargin: '200px 0px', // Start loading when image is 200px from viewport
      threshold: 0.01
    });
    
    if (imgRef.current) {
      observer.observe(imgRef.current);
    }
    
    return () => {
      if (imgRef.current) {
        observer.unobserve(imgRef.current);
      }
    };
  }, [src, lazy]);

  const handleLoad = () => {
    setIsLoaded(true);
  };

  const handleError = () => {
    setError(true);
    console.error(`Failed to load image: ${src}`);
  };

  // Define aspect ratio for the container to prevent layout shifts
  const aspectRatio = width && height ? (height / width) * 100 : 0;
  
  return (
    <div 
      className={`relative overflow-hidden ${className}`} 
      style={{ 
        backgroundColor: placeholderColor,
        paddingBottom: aspectRatio ? `${aspectRatio}%` : undefined,
      }}
    >
      {error ? (
        <div className="absolute inset-0 flex items-center justify-center bg-gray-700 text-white text-xs">
          <i className="fas fa-image-slash mr-1"></i> Failed to load
        </div>
      ) : (
        <img
          ref={imgRef}
          src={lazy ? '' : src}
          data-src={lazy ? src : undefined}
          alt={alt}
          onLoad={handleLoad}
          onError={handleError}
          style={{
            position: 'absolute',
            top: 0,
            left: 0,
            width: '100%',
            height: '100%',
            objectFit: 'cover',
            transition: 'opacity 0.3s, filter 0.5s',
            opacity: isLoaded ? 1 : 0,
            filter: isLoaded ? 'none' : 'blur(8px)',
            ...imgStyle,
            
          }}
        />
      )}
    </div>
  );
});

// Memoized Card component to prevent unnecessary re-renders
const AiPersonCard = React.memo(({ 
  content, 
  linesClass, 
  onClick 
}: { 
  content: any; 
  linesClass: string; 
  onClick: (id: string) => void;
}) => {
  const handleClick = useCallback(() => {
    onClick(content.id);
  }, [content.id, onClick]);

  // Determine image dimensions - estimate from aspect ratio to avoid layout shifts
  // Most AI generation images are 1:1 or 3:4 aspect ratio
  const imageWidth = 400; // Arbitrary base width
  const imageHeight = 700; // 5:4 aspect ratio common for portrait photos

  return (
    <div
      className="bg-card-dark rounded-xl overflow-hidden break-inside-avoid inline-block w-full cursor-pointer mb-2"
      onClick={handleClick}
    >
      <div className="relative">
        {content.isPremium && (
          <div className="absolute z-2 top-2 right-2 bg-pink-600 text-white text-xs font-bold px-2 py-1 rounded-full">
            <i className="fas fa-crown mr-1"></i> Premium
          </div>
        )}
        <ProgressiveImage
          src={content.image}
          alt={content.title}
          className="w-full"
          width={imageWidth}
          height={imageHeight}
          placeholderColor="#2a2a2a"
        />
      </div>
      <div className="p-2">
        <div className="flex justify-between items-center mb-1">
          <div className="flex items-center space-x-2">
            <div className="flex-shrink-0" >
              <ProgressiveImage
                src={content.avatar}
                alt={content.username}
                className="w-6 h-6 rounded-full object-cover object-[center_0%]"
                width={24}
                height={24}
                placeholderColor="#3a3a3a"
                imgStyle={{ objectPosition: 'center 0%' }}
              />
            </div>
            <div className="min-w-0 flex-1">
              <div className="font-semibold text-sm truncate">{content.username}</div>
              <div className="text-xs text-gray-400">{content.title}</div>
            </div>
          </div>
          {/* <button className="flex-shrink-0 bg-pink-600 text-white rounded-full px-2 py-0.5 text-xs font-semibold ml-2">
            Follow
          </button> */}
        </div>
        {content.description && (
          <div className={`text-xs text-gray-300 mt-1 mb-1 ${linesClass}`}>
            {content.description}
          </div>
        )}
        <div className="flex justify-between text-xs mt-2">
          <div className="flex space-x-2">
            <span>
              <i className="fas fa-heart text-pink-500"></i> {content.likes}
            </span>
            <span>
              <i className="fas fa-comment"></i> {content.comments}
            </span>
          </div>
          <div>
            <i className="fas fa-share-alt"></i>
          </div>
        </div>
      </div>
    </div>
  );
});

// Memoized Story component
const StoryItem = React.memo(({ story }: { story: any }) => (
  <div className="flex flex-col items-center mr-4">
    <div className="w-16 h-16 rounded-full bg-gradient-to-r from-pink-500 to-orange-500 p-0.5">
      <div className="w-full h-full rounded-full overflow-hidden bg-app-dark">
        <ProgressiveImage
          src={story.image}
          alt={story.name}
          className="w-full h-full"
          width={64}
          height={64}
          imgStyle={{ objectPosition: 'center 0%' }}
          lazy={false} // Load stories eagerly since they're above the fold
        />
      </div>
    </div>
    <span className="text-xs mt-1">{story.name}</span>
  </div>
));

// Memoized Category component
const CategoryItem = React.memo(({ category }: { category: any }) => (
  <div className="bg-gray-800 rounded-lg p-2">
    <i className={`fas ${category.icon} ${category.color} text-xl mb-1`}></i>
    <div>{category.name}</div>
  </div>
));

const Home: React.FC = () => {
  const navigate = useNavigate()
  const [showVisitorModal, setShowVisitorModal] = useState<boolean>(false)
  const [registering, setRegistering] = useState<boolean>(false)
  const [selectedContentId, setSelectedContentId] = useState<string>('')
  const [aiPersonList, setAiPersonList] = useState<any[]>([])
  const [aiPersonsByPage, setAiPersonsByPage] = useState<{[page: number]: any[]}>({})
  const [aiPersonData, setAiPersonData] = useState<any>(null)
  const [pagination, setPagination] = useState({
    page: 1,
    pageSize: 4,
    total: 0,
    totalPages: 0
  })
  const [loading, setLoading] = useState(false)
  const [hasMore, setHasMore] = useState(true)
  const [imagesLoaded, setImagesLoaded] = useState(true) // Start as true since we're using progressive loading

  // 用于加载更多的观察器目标
  const observerTarget = useRef<HTMLDivElement>(null);
  
  // Track if a request is in progress to prevent duplicate calls
  const requestInProgressRef = useRef(false);
  
  // 保存滚动位置的引用
  const scrollPositionRef = useRef(0);

  // 随机生成每个卡片description的行数限制
  const getRandomLinesClass = useCallback(() => {
    const randomNum = Math.floor(Math.random() * 3) + 2; // 随机2-4行
    return `line-clamp-${randomNum}`;
  }, []);

  // 为每个卡片预生成随机行数类，确保在重新渲染时保持一致
  // 增加依赖项确保只在需要时重新计算
  const cardLineClasses = useMemo(() => {
    // 动态调整数组大小以匹配实际数据数量或使用默认值
    const size = Math.max(aiPersonList.length, 20);
    return Array(size).fill(0).map(() => getRandomLinesClass());
  }, [getRandomLinesClass, aiPersonList.length]);

  // We no longer need to preload all images since we're using progressive loading
  // Instead, we'll just mark them as loaded immediately
  const preloadAllImages = useCallback(async (list: any[]) => {
    // Just immediately set as loaded - images will load progressively
    setImagesLoaded(true);
    return () => {};
  }, []);

  // 使用单独的状态追踪下一页请求
  const [requestingNextPage, setRequestingNextPage] = useState(false);

  // 滚动加载获取人设列表函数，使用useCallback优化性能
  const getAipersonList = useCallback(async (page = 1) => {
    // Prevent duplicate requests
    if (loading || !hasMore || requestInProgressRef.current) return;
    
    // Set request flag to prevent concurrent calls
    requestInProgressRef.current = true;
    
    // 保存当前滚动位置，不依赖于页码判断
    const currentScrollY = window.scrollY;
    scrollPositionRef.current = currentScrollY;
    
    setLoading(true);
    
    try {
      console.log(`正在请求第 ${page} 页数据...`);
      const res = await request.post('/api/ai-persons/', {
        page,
        pageSize: pagination.pageSize
      });

      if (res.status === 200) {
        const { list, pagination: newPagination } = res.data.data;
        console.log(`获取到第 ${page} 页数据，共 ${list?.length || 0} 条`);
        
        // 检查是否收到了空列表
        if (!list || list.length === 0) {
          setHasMore(false);
          return;
        }
        
        // 批量更新状态，避免多次渲染
        setAiPersonList(prev => {
          // 如果是第一页，直接替换
          if (page === 1) return list;
          
          // 否则，添加到现有列表，但避免重复
          const existingIds = new Set(prev.map(item => item.id));
          const uniqueNewItems = list.filter((item: any) => !existingIds.has(item.id));
          return [...prev, ...uniqueNewItems];
        });
        
        // 同时按页码保存数据
        setAiPersonsByPage(prev => ({
          ...prev,
          [page]: list
        }));
        
        setPagination(prevPagination => ({
          ...prevPagination,
          page: newPagination.page,
          totalPages: newPagination.totalPages,
          total: newPagination.total
        }));
        
        setHasMore(newPagination.page < newPagination.totalPages);

        // Images load progressively, so we don't need to wait
        setImagesLoaded(true);
      }
    } catch (error) {
      console.error('获取人设列表失败', error);
    } finally {
      setLoading(false);
      // Reset request flag when done
      requestInProgressRef.current = false;
      
      // 在状态更新后的下一个渲染周期恢复滚动位置
      if (page > 1) {
        window.requestAnimationFrame(() => {
          window.scrollTo({
            top: currentScrollY,
            behavior: 'auto'
          });
        });
      }
    }
  }, [loading, hasMore, pagination.pageSize]);

  // 手动加载下一页的函数
  const loadNextPage = useCallback(() => {
    if (loading || !hasMore || requestInProgressRef.current) return;
    
    const nextPage = pagination.page + 1;
    console.log(`手动触发加载第 ${nextPage} 页数据`);
    getAipersonList(nextPage);
  }, [loading, hasMore, pagination.page, getAipersonList]);

  // 初始化加载第一页 - 使用空依赖数组确保只加载一次
  useEffect(() => {
    getAipersonList(1);
    return () => {
      // 清理函数，确保标记当前没有请求进行中
      requestInProgressRef.current = false;
    };
  }, []); // Empty dependency array to ensure it only runs once

  // 替换滚动事件监听实现
  useEffect(() => {
    // 滚动事件处理函数
    const handleScroll = () => {
      // 获取滚动位置信息
      const scrollTop = document.documentElement.scrollTop || window.scrollY;
      const windowHeight = window.innerHeight;
      const documentHeight = document.documentElement.scrollHeight;
      const distanceToBottom = documentHeight - (scrollTop + windowHeight);
      
      // 检测是否触底 (阈值设置为100像素，提前加载以提高用户体验)
      const threshold = 100;
      const isAtBottom = distanceToBottom <= threshold;
      
      if (isAtBottom) {
        // 检查是否应该加载更多
        if (loading || !hasMore || requestInProgressRef.current || requestingNextPage) {
          return;
        }
        
        // 所有条件检查通过，可以加载下一页
        console.log("触发加载下一页数据");
        setRequestingNextPage(true);
        
        const nextPage = pagination.page + 1;
        console.log(`准备加载第 ${nextPage} 页数据`);
        
        getAipersonList(nextPage)
          .then(() => {
            console.log(`第 ${nextPage} 页数据加载完成`);
            setRequestingNextPage(false);
          })
          .catch((err) => {
            console.error(`第 ${nextPage} 页数据加载失败:`, err);
            setRequestingNextPage(false);
          });
      }
    };

    // 绑定滚动事件 - 使用passive提高性能
    window.addEventListener('scroll', handleScroll, { passive: true });

    // 添加初始检查，处理页面内容不足以滚动的情况
    setTimeout(() => {
      handleScroll();
    }, 1000);

    // 清理函数
    return () => {
      window.removeEventListener('scroll', handleScroll);
    };
  }, [loading, hasMore, pagination.page, getAipersonList, requestingNextPage]);

  // 第一个菜单栏 - 使用useMemo避免重新创建
  const stories = useMemo(() => [
    {
      id: '1',
      name: 'Ava_AI',
      image: 'https://knowyou.tos-cn-guangzhou.volces.com/imgs/ComfyUI_0001.png',
    },
    {
      id: '2',
      name: 'K.Dancer',
      image: 'https://knowyou.tos-cn-guangzhou.volces.com/imgs/ComfyUI_0002.png',
    },
    {
      id: '3',
      name: 'Sophie_AI',
      image: 'https://knowyou.tos-cn-guangzhou.volces.com/imgs/ComfyUI_0003.png',
    },
    {
      id: '4',
      name: 'Cosplay_AI',
      image: 'https://knowyou.tos-cn-guangzhou.volces.com/imgs/ComfyUI_0004.png',
    },
    {
      id: '5',
      name: 'Emma_ASMR',
      image: 'https://knowyou.tos-cn-guangzhou.volces.com/imgs/ComfyUI_0005.png',
    },
    {
      id: '6',
      name: 'Lisa_AI',
      image: 'https://knowyou.tos-cn-guangzhou.volces.com/imgs/ComfyUI_0006.png',
    },
  ], []);

  // 第二个菜单栏 - 使用useMemo避免重新创建  
  const categories = useMemo(() => [
    { id: '1', name: 'Trending', icon: 'fa-fire', color: 'text-orange-500' },
    { id: '2', name: 'Bikini', icon: 'fa-tshirt', color: 'text-purple-500' },
    { id: '3', name: 'Cosplay', icon: 'fa-mask', color: 'text-blue-500' },
    { id: '4', name: 'K-POP', icon: 'fa-music', color: 'text-green-500' },
  ], []);

  // 生成并注册访客UUID - 使用useCallback优化性能
  const registerVisitor = useCallback(async () => {
    try {
      setRegistering(true)
      // 使用API生成UUID
      const uuid = visitorAPI.generateUUID()
      // 调用访客注册API
      const response = await visitorAPI.register(uuid)

      if (response.success) {
        // 保存UUID和Token到本地存储
        localStorage.setItem('visitor_uuid', uuid)
        localStorage.setItem('visitor_token', response.data.token)

        // 关闭弹窗并继续跳转
        setShowVisitorModal(false)

        // 跳转到选中的内容页
        if (selectedContentId) {
          navigate(`/ai-companion/${selectedContentId}/chat`)
        }
      } else {
        console.error('访客注册失败:', response.message)
        alert('Login failed, please try again')
      }
    } catch (error) {
      console.error('访客注册出错:', error)
      alert('Login failed, please try again')
    } finally {
      setRegistering(false)
    }
  }, [navigate, selectedContentId]);

  // 点击后跳转到聊天页面 - 使用useCallback优化性能
  const handleChatNavigation = useCallback(async (id: string) => {
    // 检查是否有访客认证
    const isAuthenticated = visitorAPI.checkAuth()

    if (!isAuthenticated) {
      // 如果未认证或token已过期，显示登录弹窗
      setSelectedContentId(id)
      setShowVisitorModal(true)
      return
    }

    // 跳转到聊天页面
    navigate(`/ai-companion/${id}/chat`)
  }, [navigate]);

  return (
    <div className="min-h-screen bg-app-dark text-white pb-6 overflow-y-auto">
      {/* Add DNS Prefetching */}
      <DNSPrefetch />
      
      {/* App Header - 添加fixed定位和背景色 */}
      <div className="fixed top-0 left-0 right-0 z-50 px-4 pt-3 pb-3 flex justify-between items-center bg-app-dark border-b border-gray-800">
        <div className="text-2xl font-bold">
          Know<span className="text-pink-500">Me</span>
        </div>
        <div className="flex space-x-4">
          <i className="fas fa-bell text-xl"></i>
          <i className="fas fa-search text-xl"></i>
        </div>
      </div>

      {/* 添加占位div，防止内容被fixed header遮挡 */}
      <div className="h-[4rem]"></div>

      {/* 头部导航栏 */}
      <div className="flex overflow-x-auto px-4 pb-2 scrollbar-none" style={{ WebkitOverflowScrolling: 'touch' }}>
        {stories.map((story) => (
          <StoryItem key={story.id} story={story} />
        ))}
      </div>

      {/* 第二个菜单栏 */}
      <div className="px-4 py-3">
        <div className="flex justify-between items-center mb-3">
          <h2 className="text-lg font-bold">Explore</h2>
          <span className="text-sm text-pink-500">See All</span>
        </div>
        <div className="grid grid-cols-4 gap-2 text-center text-xs">
          {categories.map((category) => (
            <CategoryItem key={category.id} category={category} />
          ))}
        </div>
      </div>

      {/* 列表栏 */}
      <div className="px-4 py-2 overflow-auto">
        <h2 className="text-lg font-bold mb-3">Featured</h2>
        
        {/* 使用key-based持久化渲染，防止列表闪烁 */}
        <div key="content-container" className="min-h-[200px]">
          {(loading && pagination.page === 1 && aiPersonList.length === 0) ? (
            <div className="w-full py-8 flex flex-col items-center justify-center">
              <div className="animate-spin rounded-full h-8 w-8 border-b-2 border-pink-500 mb-2"></div>
              <div className="text-sm text-gray-400">Loading content...</div>
            </div>
          ) : (
            <div className="mb-6">
              {/* 将所有数据合并为一个连续流，分左右两列展示 */}
              {(() => {
                // 将所有页面的内容合并为一个数组，按页码和项目顺序排序
                const allItems: any[] = Object.entries(aiPersonsByPage)
                  .sort(([pageNumA], [pageNumB]) => parseInt(pageNumA) - parseInt(pageNumB))
                  .flatMap(([pageNum, pageItems]) => 
                    pageItems.map((item, index) => ({
                      ...item,
                      _pageNum: parseInt(pageNum),
                      _pageIndex: index
                    }))
                  );
                
                // 分成左右两列
                const leftColumnItems: any[] = [];
                const rightColumnItems: any[] = [];
                
                // 分配到左右列
                allItems.forEach((item, index) => {
                  if (index % 2 === 0) {
                    leftColumnItems.push(item);
                  } else {
                    rightColumnItems.push(item);
                  }
                });
                
                return (
                  <div className="grid grid-cols-2 gap-4">
                    {/* 左列 */}
                    <div className="flex flex-col space-y-1">
                      {leftColumnItems.map((content, idx) => (
                        <div key={content.id}>
                          <AiPersonCard 
                            content={content} 
                            linesClass={cardLineClasses[idx * 2]} 
                            onClick={handleChatNavigation} 
                          />
                        </div>
                      ))}
                    </div>
                    
                    {/* 右列 */}
                    <div className="flex flex-col space-y-1">
                      {rightColumnItems.map((content, idx) => (
                        <div key={content.id}>
                          <AiPersonCard 
                            content={content} 
                            linesClass={cardLineClasses[idx * 2 + 1]} 
                            onClick={handleChatNavigation} 
                          />
                        </div>
                      ))}
                    </div>
                  </div>
                );
              })()}
            </div>
          )}
        </div>
        
        {/* 加载更多区域，使用点击加载和滚动加载两种方式 */}
        <div className="w-full py-1 flex justify-center items-center mt-4" ref={observerTarget}>
          {loading && pagination.page > 1 ? (
            <div className="animate-spin rounded-full h-2 w-8 border-b-2 border-pink-500"></div>
          ) : hasMore ? (
            <div className="text-gray-400 text-sm">Pull up to load more</div>
          ) : aiPersonList.length > 0 ? (
            <div className="text-gray-400 text-sm">There's no more content left</div>
          ) : null}
        </div>
      </div>

      {/* 游客登录弹窗 */}
      {showVisitorModal && (
        <div className="fixed inset-0 bg-black bg-opacity-70 flex items-center justify-center z-50">
          <div className="bg-[#1e1e1e] rounded-xl p-5 max-w-sm w-[85%] border border-gray-700 shadow-lg">
            <div className="text-center mb-5">
              <div className="text-2xl font-bold mb-2">Visitor login</div>
              <p className="text-gray-400 text-sm">
                You will need to log in as a guest before you can continue your visit. Once you've logged in, you'll be assigned a temporary account.
              </p>
            </div>

            <div className="flex justify-center gap-3 mt-6">
              <button
                onClick={() => setShowVisitorModal(false)}
                className="px-5 py-2 bg-gray-700 text-white rounded-lg"
              >
                Cancel
              </button>
              <button
                onClick={registerVisitor}
                disabled={registering}
                className={`px-5 py-2 bg-pink-600 text-white rounded-lg flex items-center justify-center min-w-[100px] ${registering ? 'opacity-70' : 'hover:bg-pink-700'
                  }`}
              >
                {registering ? (
                  <>
                    <div className="w-4 h-4 border-2 border-white border-t-transparent rounded-full animate-spin mr-2"></div>
                    Logging in...
                  </>
                ) : (
                  'Log in now'
                )}
              </button>
            </div>
          </div>
        </div>
      )}
    </div>
  )
}

export default React.memo(Home) 